﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using DOMercury.Interfaces;
using DOMercury.Engine;
using DOMercury.Items;
using System.Windows.Media.Animation;

namespace Bezel__
{
    /// <summary>
    /// Interaction logic for Window1.xaml
    /// </summary>
    public partial class Bezel3 : Window, IDOMercuryUserInterface
    {
        private Storyboard Expand, Contract, Blur;
        private bool persist = false;
        private bool reset = true;
        private bool firstEver = true;
        private bool expanded = false;
        private bool deactivateAnimating = false;
        private System.Windows.Forms.AutoCompleteMode ACM;
        private System.Windows.Forms.AutoCompleteSource ACS;
        private System.Windows.Forms.AutoCompleteStringCollection ACSC;
        private ItemList itemsList, paramsList;
        private ActionList actionsList;

        
        public Bezel3()
        {
            InitializeComponent();
            
            DOMercuryCoreManager.Instance.OnChangeActionList += new ChangeIActionListHandler(DOMercuryCoreManager_OnChangeActionList);
            DOMercuryCoreManager.Instance.OnChangeItemList += new ChangeIItemListHandler(DOMercuryCoreManager_OnChangeItemList);
            DOMercuryCoreManager.Instance.OnChangeParamList += new ChangeIItemListHandler(DOMercuryCoreManager_OnChangeParamList); DOMercuryCoreManager.Instance.OnChangeCurrentAction += new ChangeIActionHandler(Core_OnChangeCurrentAction);
            DOMercuryCoreManager.Instance.OnChangeCurrentItem += new ChangeIItemHandler(Core_OnChangeCurrentItem);
            DOMercuryCoreManager.Instance.OnChangeCurrentParam += new ChangeIItemHandler(Core_OnChangeCurrentParam);
            DOMercuryCoreManager.Instance.OnInputChanged += new InputChangedHandler(DOMercuryCoreManager_OnInputChanged);
            DOMercuryCoreManager.Instance.OnParamInputChanged +=new InputChangedHandler(DOMercuryCoreManager_OnParamInputChanged);
            DOMercuryCoreManager.Instance.OnStateChanged += new StateChangedHandler(DOMercuryCoreManager_OnStateChanged);
            DOMercuryCoreManager.Instance.OnTextModeToggled += new TextModeToggledHandler(DOMercuryCoreManager_OnTextModeToggled);
            DOMercuryCoreManager.Instance.OnHideForm += new HideFormHandler(DOMercuryCoreManager_OnHideForm);
            DOMercuryCoreManager.Instance.OnIncrementList += new GeneralEventHandler(Instance_OnIncrementList);
            DOMercuryCoreManager.Instance.OnDecrementList += new GeneralEventHandler(Instance_OnDecrementList);
            Expand = (Storyboard)FindResource("Expand");
            Contract = (Storyboard)FindResource("Contract");
            Blur = (Storyboard)FindResource("Blur");
            Blur.Completed += new EventHandler(Blur_Completed);
            itemsList = new ItemList(ListSelectorType.Item);
            actionsList = new ActionList(ListSelectorType.Action);
            paramsList = new ItemList(ListSelectorType.Param);
            itemsList.Activated += new EventHandler(List_Activated);
            actionsList.Activated += new EventHandler(List_Activated);
            paramsList.Activated += new EventHandler(List_Activated);
            //itemsList.SetDragMove(this);
            //actionsList.SetDragMove(this);
            //paramsList.SetDragMove(this);
            DOMercuryCoreManager.Instance.Initialize(itemsList, actionsList, paramsList);
            Contract.Begin(this);
            ItemDisplayer.Active = true;
            ActionDisplayer.Active = false;
            ParamDisplayer.Active = false;

            //this.Show();
            //this.DeactivateForm();
        }

        void Blur_Completed(object sender, EventArgs e)
        {
            FinishDeactivatingForm();
        }

        void List_Activated(object sender, EventArgs e)
        {
            this.Activate();
        }

        void Instance_OnDecrementList(object sender)
        {
            DecrementCurrentList();
        }

        void Instance_OnIncrementList(object sender)
        {
            IncrementCurrentList();
        }

        void DOMercuryCoreManager_OnChangeParamList(object sender, List<IItem> Items)
        {

            paramsList.ItemsSource.Clear();
            paramsList.ItemsSource = Items;
            if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Params)
            {
                if (Items.Count > 0)
                {
                    SetParamListVisible(true);
                }
                else
                {
                    SetParamListVisible(false);
                }
            }

        }

        private void SetParamListVisible(bool visible)
        {
            
            if (visible)
            {
                persist = true;
                if (ParamDisplayer.IsVisible)
                {
                    paramsList.Left = ParamDisplayer.PointToScreen(new Point(0, 0)).X;
                    paramsList.Top = this.Top + border.ActualHeight -5;
                }
            }
            paramsList.CurrentlyVisible = visible;
        }

        void DOMercuryCoreManager_OnChangeItemList(object sender, List<IItem> Items)
        {

            itemsList.ItemsSource.Clear();
            itemsList.ItemsSource = Items;
            if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Items)
            {
                if (Items.Count > 0)
                {
                    SetItemListVisible(true);
                }
                else
                {
                    SetItemListVisible(false);
                }
            }


        }

        public void DecrementCurrentList()
        {

            if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Items)
            {
                itemsList.DecrementItem();
            }
            else if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Actions)
            {
                actionsList.DecrementItem();
            }
            else
            {
                paramsList.DecrementItem();
            }
        }

        private void IncrementCurrentList()
        {
            if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Items)
            {
                itemsList.IncrementItem();
            }
            else if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Actions)
            {
                actionsList.IncrementItem();
            }
            else
            {
                paramsList.IncrementItem();
            }
        }

        private void SetItemListVisible(bool visible)
        {

            //time for an ugly hack!
            if (firstEver)
            {
                firstEver = false;
            }
            else
            {
                if (visible)
                {
                    persist = true;
                    if (ItemDisplayer.IsVisible)
                    {
                        itemsList.Left = ItemDisplayer.PointToScreen(new Point(0, 0)).X;
                        itemsList.Top = this.Top + border.ActualHeight -5;
                    }
                }
                if (itemsList.ItemsSource.Count > 0)
                {
                    itemsList.CurrentlyVisible = visible;
                }
                else
                {
                    itemsList.CurrentlyVisible = false;
                }
            }
        }

        void DOMercuryCoreManager_OnChangeActionList(object sender, List<IAction> Actions)
        {

            actionsList.ItemsSource = Actions;
            if (DOMercuryCoreManager.Instance.CurrentState == CurrentState.Actions)
            {
                if (Actions.Count > 0)
                {
                    SetActionListVisible(true);
                }
                else
                {
                    SetActionListVisible(false);
                }
            }

        }

        private void SetActionListVisible(bool visible)
        {
            
            if (visible)
            {
                persist = true;
                if (ActionDisplayer.IsVisible)
                {
                    actionsList.Left = ActionDisplayer.PointToScreen(new Point(0, 0)).X;
                    actionsList.Top = this.Top + border.ActualHeight -5;
                    Console.WriteLine("actionsList Top: " + actionsList.Top + " Left: " + actionsList.Left);
                }
            }
            actionsList.CurrentlyVisible = visible;
        }

        void DOMercuryCoreManager_OnHideForm(object sender, bool Reset)
        {
            reset = Reset;
            DeactivateForm();
        }

        void DOMercuryCoreManager_OnTextModeToggled(object sender, bool textMode)
        {
            //Toggle ItemPane TextMode
        }

        void DOMercuryCoreManager_OnStateChanged(object sender, CurrentState newState)
        {
            persist = true;
            switch (newState)
            {
                case CurrentState.Items:
                    ActivateItemDisplayer(); 
                    SetParamListVisible(false);
                    SetActionListVisible(false);
                    SetItemListVisible(true);
                    break;
                case CurrentState.Actions:
                    ActivateActionDisplayer(); 
                    SetParamListVisible(false);
                    SetActionListVisible(true);
                    SetItemListVisible(false);
                    break;
                default:
                    ActivateParamDisplayer();
                    SetParamListVisible(true);
                    SetActionListVisible(false);
                    SetItemListVisible(false);
                    break;
            }
            persist = false;

        }

        private void ActivateParamDisplayer()
        {
            ExpandParamPane();
            ParamDisplayer.Active = true;
            ActionDisplayer.Active = false;
            ItemDisplayer.Active = false;
        }

        private void ActivateActionDisplayer()
        {
            ContractParamPane();
            ActionDisplayer.Active = true;
            ParamDisplayer.Active = false;
            ItemDisplayer.Active = false;
        }

        private void ActivateItemDisplayer()
        {
            ContractParamPane();
            ItemDisplayer.Active = true;
            ParamDisplayer.Active = false;
            ActionDisplayer.Active = false;
        }

        private void ContractParamPane()
        {
            if (expanded)
            {
                Contract.Begin(this);
                expanded = false;
            }
        }

        private void ExpandParamPane()
        {
            if (!expanded)
            {
                Expand.Begin(this);
                expanded = true;
            }
        }

        void DOMercuryCoreManager_OnInputChanged(object myObject, string newInput)
        {
            txtItem.Content = newInput;
        }

        void DOMercuryCoreManager_OnParamInputChanged(object myObject, string newInput)
        {
            txtParam.Content = newInput;
        }

        void Core_OnChangeCurrentParam(object myObject, IItem Item)
        {
            ItemDisplayer.FoundItems = DOMercuryCoreManager.Instance.FoundParamPaths;
            ParamDisplayer.CurrentItem = DOMercuryCoreManager.Instance.CurrentParam;
        }

        void Core_OnChangeCurrentItem(object myObject, IItem Item)
        {
            ItemDisplayer.FoundItems = DOMercuryCoreManager.Instance.FoundItemPaths;
            ItemDisplayer.CurrentItem = DOMercuryCoreManager.Instance.CurrentItem;
            
        }

        void Core_OnChangeCurrentAction(object myObject, IAction Action)
        {
            ActionDisplayer.CurrentAction = DOMercuryCoreManager.Instance.CurrentAction;
        }

        #region IDOMercuryUserInterface Members

        public void ActivateForm()
        {            
            
            DOMercuryCoreManager.Instance.CurrentState = CurrentState.Items;
            try
            {
                this.Show();
            }
            catch { }
            this.Topmost = true;
            DOMercuryCoreManager.Instance.SearchForFoundItems();
            this.Opacity = 1;
            this.Activate();
            this.Focus();
            
            
        }

        public void CloseForm()
        {
            this.Close();
        }

        public void DeactivateForm()
        {
            if (!deactivateAnimating)
            {
                deactivateAnimating = true;
                Blur.Begin(this);
                if (reset)
                {
                    DOMercuryCoreManager.Instance.ItemInput = "";
                    Interface.EngineCore.ReturnMainIndex();
                    ItemDisplayer.ClearDisplayer();
                    ActionDisplayer.ClearDisplayer();
                    ParamDisplayer.ClearDisplayer();
                    itemsList.ClearItemsSource();
                    actionsList.ClearItemsSource();
                    paramsList.ClearItemsSource();
                }

                GC.Collect();
                reset = true;
                SetParamListVisible(false);
                SetActionListVisible(false);
                SetItemListVisible(false);
            }
            
        }

        private void FinishDeactivatingForm()
        {
            this.Opacity = 0;
            this.Topmost = false;
            deactivateAnimating = false;
            //Windows.FocusHelper.sendWindowToBack(this);
        }

        public void DisplayOptions()
        {
            //When options form is built, show it here
        }

        public bool HasOptions
        {
            get { return false; }
        }


        #endregion
     

        private void Window_MouseDown(object sender, MouseButtonEventArgs e)
        {
            try
            {
                this.DragMove();
                SetItemListVisible(itemsList.CurrentlyVisible);
                SetActionListVisible(actionsList.CurrentlyVisible);
                SetParamListVisible(paramsList.CurrentlyVisible);
            }
            catch
            {
                //No drag for you!
            }

        }

        private void Window_KeyDown(object sender, KeyEventArgs e)
        {
            DOMercuryCoreManager.Instance.DoKeyDown(sender, e);
        }

        private void Window_TextInput(object sender, TextCompositionEventArgs e)
        {
            DOMercuryCoreManager.Instance.DoTextInput(sender, e);
        }


        private void Window_Deactivated(object sender, EventArgs e)
        {
            
            if (!persist)
            {
                DeactivateForm();
            }

            //persist = false;
        }

    }

}
